package com.acme.bankapp.service.bank;

import java.io.File;
import java.io.FileWriter;
import java.io.IOException;

import com.acme.bankapp.domain.bank.Bank;
import com.acme.bankapp.domain.bank.CheckingAccount;
import com.acme.bankapp.domain.bank.Client;
import com.acme.bankapp.domain.bank.ClientRegistrationListener;
import com.acme.bankapp.domain.bank.Gender;

public class BankService {
	public Bank createNewBank() {
		Bank bank = new Bank();
		return bank;
	}

	public static void printMaximumAmountToWithdraw(Bank bank)
			throws AccountDoesntExistsException {
		Client[] clients = bank.getClients();
		for (Client i : clients) {
			if (i != null) {
				System.out.println("MaximumAmounttoWithdraw for "
						+ i.getClientSalutation() + " is "
						+ i.getAccount().maximumAmountToWithdraw());
			}

		}
	}

	public static Client addClient(Bank bank, String name, Gender gender)
			throws ClientExistsException, AccountDoesntExistsException,
			IOException {
		Client[] clients = bank.getClients();
		for (Client i : clients) {
			if (i != null && i.getName() == name)
				throw new ClientExistsException();
		}
		ClientRegistrationListener[] listeners = bank.getListeners();
		for (int i = 0; i < clients.length; i++) {
			if (clients[i] == null) {
				Client client = new Client();
				clients[i] = client;
				clients[i].setName(name);
				clients[i].setGender(gender);
				for (ClientRegistrationListener l : listeners) {
					l.onClientAdded(clients[i]);
				}
				return clients[i];
			}
		}
		return null;
	}

	public static void printBalance(Bank bank)
			throws AccountDoesntExistsException {
		System.out.println();
		Client[] clients = bank.getClients();
		{
			for (Client i : clients) {
				if (i != null) {
					System.out.println(i.getClientSalutation()
							+ "'s balance = " + i.getAccount().toString());

				}
			}
			System.out.println();
		}
	}

	public static void readBank() throws ClientExistsException, IOException,
			AccountDoesntExistsException {
		File file = new File("c:/myjava/feed.txt");
		if (file.exists() && file.isFile() && file.canRead()) {
			BankDataLoaderServise.parseFeed(file);
		}
	}

	public static void saveBank(Bank bank) throws AccountDoesntExistsException,
			IOException {
		File file = new File("c:/myjava/feed.txt");
		if (file.exists() && file.isFile() && file.canWrite()) {
			Client[] clients = bank.getClients();
			FileWriter writer = new FileWriter("c:/myjava/feed.txt");
			for (Client cl : clients) {
				if (cl != null) {
					String clientInfoString = makeClientInfoString(cl);
					writer.write(clientInfoString + "\n");
				}
			}
			writer.close();
		}
	}

	public static String makeClientInfoString(Client cl)
			throws AccountDoesntExistsException {
		StringBuffer sbuf = new StringBuffer();
		if (cl.getAccount().getClass().getSimpleName()
				.equals("CheckingAccount")) {
			sbuf.append("accounttype=c;");
			sbuf.append("balance=" + cl.getAccount().getBalance() + ";");
			CheckingAccount a = (CheckingAccount) cl.getAccount();
			sbuf.append("overdraft=" + a.getOverdraft() + ";");
			sbuf.append("name=" + cl.getName() + ";");
			if (cl.getGender() == Gender.MALE) {
				sbuf.append("gender=m;");
			} else {
				sbuf.append("gender=f;");
			}
		} else {
			sbuf.append("accounttype=s;");
			sbuf.append("balance=" + cl.getAccount().getBalance() + ";");
			sbuf.append("name=" + cl.getName() + ";");
			if (cl.getGender() == Gender.MALE) {
				sbuf.append("gender=m;");
			} else {
				sbuf.append("gender=f;");
			}
		}
		return sbuf.toString();
	}

	public static void modifyBank(Bank bank) throws NotEnoughFundsException,
			AccountDoesntExistsException, IOException {
		System.out.println();
		modifyWithdraw(bank, 0, 90000.0);
		modifyDeposit(bank, 1, 150000.0);
		System.out.println("Accounts modification finished");
		saveBank(bank);
	}

	public static void modifyDeposit(Bank bank, int clientNumber, Double amount)
			throws AccountDoesntExistsException {
		if (bank != null) {
			Client[] clients = bank.getClients();
			if (clients[clientNumber] != null) {
				System.out.println("Modifying "
						+ clients[clientNumber].getClientSalutation()
						+ "'s account...");
				clients[clientNumber].getAccount().deposit(amount);
			}
		}
	}

	public static void modifyWithdraw(Bank bank, int clientNumber, Double amount)
			throws AccountDoesntExistsException {
		if (bank != null) {
			Client[] clients = bank.getClients();
			if (clients[clientNumber] != null) {
				System.out.println("Modifying "
						+ clients[clientNumber].getClientSalutation()
						+ "'s account...");
				clients[clientNumber].getAccount().deposit(amount);
			}
		}
	}
}
